#include "widget.h"
#include <QPainter>
#include <QPen>
#include <QBrush>
#include <QDebug>
#include <chess_pieces.h>
Widget::Widget(QString ip,int port,QWidget *parent)
    : QWidget(parent)
{
    // set_ske(0, 0, "C:\\Users\\pg\\Desktop\\check\\img\\redcar.png");
    initCheckerboard(red, black);
    socket_com = new QTcpSocket(this);
    posfirst = QPoint(Boundary_max_x + 1, Boundary_max_y + 1);
    wait_label_img=new QLabel(this);
    movie=new QMovie(":/img/wait.gif");
    wait_label_img->setMovie(movie);
    movie->start();

    QVBoxLayout *vboxlayout=new QVBoxLayout;
    vboxlayout->addWidget(wait_label_img);
    this->setLayout(vboxlayout);

    socket_com->connectToHost(ip, port);

    connect(socket_com, SIGNAL(readyRead()), this, SLOT(recvMSG()));

}

//数据接收
void Widget::recvMSG()
{
    ComData data;
    socket_com->read((char *)&data, sizeof(ComData));
    if (data.type_cmd == ChangeChess)
    {
        //对方走子，请更新棋盘
        if (CAMP == RED)
            changeChessboard(black, red, &data);
        else if (CAMP == BLACK)
            changeChessboard(red, black, &data);
        //允许己方走步
        xuanzhongflag = 0;
        qDebug() << "你可以走了";
        Allowed_run = true;
        update();
    }
    else if (data.type_cmd == Cat_effectively)
    {
        //己方走子有效,更新棋盘
        qDebug() << "己方走子有效,更新棋盘";
        if (CAMP == RED)
            changeChessboard(red, black, &data);
        else if (CAMP == BLACK)
            changeChessboard(black, red, &data);

        //禁止己方走步
        Allowed_run = false;
        update();
    }
    else if (data.type_cmd == Cat_uneffectively)
    {
        //己方走子无效，重新走子  (理论上服务器可以检测走子是否有效，但是目前仅由走子的行动函数判断是否有效)，
        //所以目前服务器不会返回走子无效
    }
    else if (data.type_cmd == Red_cmd)
    {
        //服务器 指定当前客户端为 红方 红方先行
        CAMP = RED;
        Allowed_run = true;
        update();
    }
    else if (data.type_cmd == Black_cmd)
    {
        //服务器 指定当前客户端为 黑方
        CAMP = BLACK;
        Allowed_run = false;
        update();
    }
    else if (data.type_cmd == Win)
    {
        //胜利
        win=new win_losser(true);
        this->hide();
        win->show();
    }
    else if (data.type_cmd == Fail)
    {
        //失败
        loss=new win_losser(false);
        this->hide();
        loss->show();
    }
}

//只 更新棋子位置，不做胜利以及位置有效判断，（胜利判断由服务器做），位置有效判断由棋子的具体行动函数做
int Widget::changeChessboard(QVector<chess_pieces> &action_camp, QVector<chess_pieces> &Waiting_camp, const ComData *data)
{
    Position pos_tmep;

    // 若有重叠则吃掉等待方棋子
    QVector<chess_pieces>::iterator position_itr = Waiting_camp.begin();
    for (int i = 0; i < Waiting_camp.size(); i++)
    {
        pos_tmep = Waiting_camp[i].getPosition();
        if (pos_tmep.x == data->change.target_pos.x && pos_tmep.y == data->change.target_pos.y)
        {
            if (Will == Waiting_camp[i].getChessType())
            {
                // 等待方元帅被吃了 —— 游戏结束
                return Win;
            }
            // 吃掉了等待方的这颗棋子
            Waiting_camp.erase(position_itr + i);
            break;
        }
    }
    // 更新行动方当前棋子位置
    for (int i = 0; i < action_camp.size(); i++)
    {
        if (data->change.chess.chess_type == action_camp[i].getChessType())
        {
            action_camp[i].setPosition(data->change.target_pos);
            break;
        }
    }
    return Cat_effectively;
}

void Widget::set_ske(int skex, int skey, QString filepath)
{
    QPixmap pix(filepath);
    pix = pix.scaled((99.0 / 864) * background.width(), (99.0 / 864) * background.width());
    this->skex = skex * (99.0 / 864) * background.width();
    this->skey = skey * (99.0 / 864) * background.width();
    this->filepath = filepath;
}

void Widget::paintEvent(QPaintEvent *event)
{

    if (CAMP == RED || CAMP == BLACK)
    {
        wait_label_img->hide();
        QPainter p(this);
        // QPixmap background(":/../img/checkerboard.jpg");
        background = QPixmap(":/./img/checkerboard.jpg");
        background = background.scaled(this->width(), this->height(), Qt::KeepAspectRatio);
        p.drawPixmap(abs(this->width() - background.width()) / 2, 0, background);

        l_left = (36.0 / 864) * background.width();
        l_right = (35.0 / 864) * background.width();
        l_top = (41.0 / 961) * background.height();
        l_down = (28.0 / 961) * background.height();

        p.translate(abs(this->width() - background.width()) / 2 + l_left, 0 + l_top); //移动坐标系

        if (CAMP == BLACK)
        {
            for (int i = 0; i < red.length(); i++)
            {
                set_ske(red[i].getPosition().x, red[i].getPosition().y, red[i].getfilepath());
                QPixmap pix(filepath);
                pix = pix.scaled((99.0 / 864) * background.width(), (99.0 / 864) * background.width(), Qt::KeepAspectRatio);
                p.drawPixmap(skex - pix.width() / 2, skey - pix.width() / 2, pix);
            }
            for (int i = 0; i < black.length(); i++)
            {
                set_ske(black[i].getPosition().x, black[i].getPosition().y, black[i].getfilepath());
                QPixmap pix(filepath);
                if (black[i].getPosition().x == posfirst.x() && black[i].getPosition().y == posfirst.y() && xuanzhongflag == 0 && Allowed_run)
                {
                    xuanzhongflag = 1;
                    select_chess = &black[i];
                    //选中之后赋颜色
                    pix.fill(Qt::TransparentMode);
                    posfirst = QPoint(Boundary_max_x + 1, Boundary_max_y + 1);
                    qDebug() << "新位置" << posfirst;
                }
                pix = pix.scaled((99.0 / 864) * background.width(), (99.0 / 864) * background.width(), Qt::KeepAspectRatio);
                p.drawPixmap(skex - pix.width() / 2, skey - pix.width() / 2, pix);
            }
        }
        else if (CAMP == RED)
        {
            for (int i = 0; i < red.length(); i++)
            {
                set_ske(red[i].getPosition().x, Boundary_max_y - red[i].getPosition().y, red[i].getfilepath());
                QPixmap pix(filepath);
                if (red[i].getPosition().x == posfirst.x() && red[i].getPosition().y == posfirst.y() && xuanzhongflag == 0 && Allowed_run)
                {
                    select_chess = &red[i];
                    xuanzhongflag = 1;
                    //选中之后赋颜色
                    pix.fill(Qt::TransparentMode);
                    qDebug() << "赋予颜色";
                    posfirst = QPoint(Boundary_max_x + 1, Boundary_max_y + 1);
                    qDebug() << "新位置" << posfirst;
                }
                pix = pix.scaled((99.0 / 864) * background.width(), (99.0 / 864) * background.width(), Qt::KeepAspectRatio);
                p.drawPixmap(skex - pix.width() / 2, skey - pix.width() / 2, pix);
            }
            for (int i = 0; i < black.length(); i++)
            {
                set_ske(black[i].getPosition().x, Boundary_max_y - black[i].getPosition().y, black[i].getfilepath());
                QPixmap pix(filepath);
                pix = pix.scaled((99.0 / 864) * background.width(), (99.0 / 864) * background.width(), Qt::KeepAspectRatio);
                p.drawPixmap(skex - pix.width() / 2, skey - pix.width() / 2, pix);
            }
        }
    }else{
        // 在等待
        QVBoxLayout *vboxlayout=new QVBoxLayout;
        vboxlayout->addWidget(wait_label_img);
        this->setLayout(vboxlayout);
    }
}

void Widget::mousePressEvent(QMouseEvent *event)
{
    if (Allowed_run)
    {
        if (0 == xuanzhongflag)
        {
            QPoint first = event->pos();
            double x = first.x() - abs(this->width() - background.width()) / 2 - l_left;  //算x的在棋盘的坐标
            double y = first.y() - abs(this->height() - background.height()) / 2 - l_top; //算y在棋盘的坐标
            x = x / ((99.0 / 864) * background.width());
            y = y / ((99.0 / 864) * background.width());

            x = qRound(x);
            y = qRound(y);
            if (x < 0 || y < 0)
                return;
            if (x > 8 || y > 9)
                return;
            if (CAMP == RED)
                posfirst = QPoint(x, Boundary_max_y - y);
            else if (CAMP == BLACK)
                posfirst = QPoint(x, y);
            qDebug() << "第一次点击位置" << posfirst;
            update();
        }
        else if (1 == xuanzhongflag)
        {
            QPoint first = event->pos();
            double x = first.x() - abs(this->width() - background.width()) / 2 - l_left;  //算x的在棋盘的坐标
            double y = first.y() - abs(this->height() - background.height()) / 2 - l_top; //算y在棋盘的坐标
            x = x / ((99.0 / 864) * background.width());
            y = y / ((99.0 / 864) * background.width());

            x = qRound(x);
            y = qRound(y);
            if (x < 0 || y < 0)
                return;
            if (x > 8 || y > 9)
                return;
            if (CAMP == RED)
                possecend = QPoint(x, Boundary_max_y - y);
            else if (CAMP == BLACK)
                possecend = QPoint(x, y);
            qDebug() << "第二次点击位置" << possecend;

            //判断棋子目标坐标是否有效
            if (select_chess->IsActionEfficacious(CAMP, possecend, red, black))
            {
                qDebug() << "走子有效";
                //有效发送 坐标至服务器
                ComData data_chess;
                Position target_pos = {.x = (unsigned int)possecend.x(), .y = (unsigned int)possecend.y()};
                data_chess.type_cmd = ChangeChess;
                data_chess.change.chess = select_chess->getChessInfo();
                data_chess.change.target_pos = target_pos;
                socket_com->write((char *)&data_chess, sizeof(ComData));
                qDebug() << "走子有效数据已发送";
            }
            else
            {
                //无效
                qDebug() << "走子无效";
                xuanzhongflag = 0;
            }
            update();
        }
    }
}

void Widget::initCheckerboard(QVector<chess_pieces> &red, QVector<chess_pieces> &black)
{
    red.clear();
    black.clear();

    Position pos = {0, 0};
    // 红棋
    red.push_back(chess_pieces(RED, CarLeft, pos, ":/./img/redcar.png"));
    pos = {8, 0};
    red.push_back(chess_pieces(RED, CarRight, pos, ":/./img/redcar.png"));
    pos = {1, 0};
    red.push_back(chess_pieces(RED, HorseLeft, pos, ":/./img/redhorse.png"));
    pos = {7, 0};
    red.push_back(chess_pieces(RED, HorseRight, pos, ":/./img/redhorse.png"));
    pos = {2, 0};
    red.push_back(chess_pieces(RED, ElephantLeft, pos, ":/./img/redelephant.png"));
    pos = {6, 0};
    red.push_back(chess_pieces(RED, ElephantRight, pos, ":/./img/redelephant.png"));
    pos = {3, 0};
    red.push_back(chess_pieces(RED, BachelorLeft, pos, ":/./img/redbachelor.png"));
    pos = {5, 0};
    red.push_back(chess_pieces(RED, BachelorRight, pos, ":/./img/redbachelor.png"));
    pos = {4, 0};
    red.push_back(chess_pieces(RED, Will, pos, ":/./img/redwill.png"));

    pos = {1, 2};
    red.push_back(chess_pieces(RED, GunLeft, pos, ":/./img/redgun.png"));
    pos = {7, 2};
    red.push_back(chess_pieces(RED, GunRight, pos, ":/./img/redgun.png"));

    pos = {0, 3};
    red.push_back(chess_pieces(RED, Redarms1, pos, ":/./img/redarms.png"));
    pos = {2, 3};
    red.push_back(chess_pieces(RED, Redarms2, pos, ":/./img/redarms.png"));
    pos = {4, 3};
    red.push_back(chess_pieces(RED, Redarms3, pos, ":/./img/redarms.png"));
    pos = {6, 3};
    red.push_back(chess_pieces(RED, Redarms4, pos, ":/./img/redarms.png"));
    pos = {8, 3};
    red.push_back(chess_pieces(RED, Redarms5, pos, ":/./img/redarms.png"));

    // 黑棋
    pos = {0, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, CarLeft, pos, ":/./img/blackcar.png"));
    pos = {8, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, CarRight, pos, ":/./img/blackcar.png"));
    pos = {1, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, HorseLeft, pos, ":/./img/blackhorse.png"));
    pos = {7, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, HorseRight, pos, ":/./img/blackhorse.png"));
    pos = {2, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, ElephantLeft, pos, ":/./img/blackelephant.png"));
    pos = {6, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, ElephantRight, pos, ":/./img/blackelephant.png"));
    pos = {3, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, BachelorLeft, pos, ":/./img/blackbachelor.png"));
    pos = {5, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, BachelorRight, pos, ":/./img/blackbachelor.png"));
    pos = {4, Boundary_max_y - 0};
    black.push_back(chess_pieces(BLACK, Will, pos, ":/./img/blackwill.png"));

    pos = {1, Boundary_max_y - 2};
    black.push_back(chess_pieces(BLACK, GunLeft, pos, ":/./img/blackgun.png"));
    pos = {7, Boundary_max_y - 2};
    // pos = {7, Boundary_max_y - 6};
    black.push_back(chess_pieces(BLACK, GunRight, pos, ":/./img/blackgun.png"));

    pos = {0, Boundary_max_y - 3};
    black.push_back(chess_pieces(BLACK, Redarms1, pos, ":/./img/blackarms.png"));
    pos = {2, Boundary_max_y - 3};
    black.push_back(chess_pieces(BLACK, Redarms2, pos, ":/./img/blackarms.png"));
    pos = {4, Boundary_max_y - 3};
    black.push_back(chess_pieces(BLACK, Redarms3, pos, ":/./img/blackarms.png"));
    pos = {6, Boundary_max_y - 3};
    black.push_back(chess_pieces(BLACK, Redarms4, pos, ":/./img/blackarms.png"));
    pos = {8, Boundary_max_y - 3};
    black.push_back(chess_pieces(BLACK, Redarms5, pos, ":/./img/blackarms.png"));
}
Widget::~Widget()
{
}
